home *** CD-ROM | disk | FTP | other *** search
/ Language/OS - Multiplatform Resource Library / LANGUAGE OS.iso / rexx / imc / rexx-imc.5 / rexx.tech < prev    next >
Encoding:
Text File  |  1993-06-25  |  32.5 KB  |  689 lines

  1.  
  2. The REXX/imc Technical Reference
  3.  
  4. This reference contains information for programmers of functions and other
  5. utilities to be called by (or to call) the Rexx interpreter.
  6.  
  7. Information for Rexx programmers can be found in rexx.summary, rexx.info and
  8. rexx.ref.
  9.  
  10.  
  11. 1. Writing executable functions for REXX
  12.  
  13. Synopsis:  #include "functions.h"
  14.            #include "ext.h"            /* optional */
  15.  
  16.            dictionary rxdictionary[];  /* optional */
  17.        
  18.        int rxfunction(name,argc)
  19.        char *name;
  20.        int argc;
  21.  
  22. There are two general ways to package REXX functions:
  23.  
  24.  (a) with a single function in each file, and
  25.  (b) with multiple functions in one file (this will be called a package).
  26.  
  27. In case (a), a file called "foo.rxfn" will be called by the function call
  28. "foo()" in a REXX program.  In case (b), REXX will need some help from the
  29. programmer in order to know when to load a package to call a particular
  30. function.  This can be done in two ways:
  31.  
  32.  (b.i)  Give the package multiple names, by using symbolic (or hard) links.
  33.         That is, if a package contains two functions, to be called from REXX
  34.     as "foo()" and "bar()", then it may be stored in "foo.rxfn" and
  35.     linked to "bar.rxfn".  Once either of foo() or bar() have been
  36.     called, both will be loaded and can be used without problems.
  37.  
  38.  (b.ii) Give the package a name such as "foo_init.rxfn" and insist that the
  39.         REXX programmer always calls "foo_init()" first before using any
  40.     other function in the package.  This function will typically just
  41.     stack "0" and return, but in the meantime REXX will have loaded all
  42.     the functions from the package so that they can be used by the
  43.     program.
  44.  
  45. The set of mathematical functions, rxmathfn.rxfn, is an example of the first
  46. method above, but since the interpreter is programmed to interpret "sin",
  47. "cos", etc. as symbolic links to "rxmathfn", those links do not need to be
  48. physically present.
  49.  
  50. A single REXX function file should contain a public symbol called
  51. "rxfunction" declared as in the synopsis above, and no dictionary.
  52.  
  53. A function package should contain a public symbol called "rxdictionary"
  54. declared as above, containing the names and addresses of all the functions.
  55. Each of the functions should be declared in the same way as "rxfunction"
  56. above.  A package called "foo.rxfn" may, in addition, supply the symbol
  57. "rxfunction" to implement the function "foo()", but only if the name "FOO"
  58. is not in the dictionary.
  59.  
  60. The definition of the dictionary structure is as follows (in "const.h",
  61. included from "functions.h"):
  62.  
  63. typedef struct _dictionary {
  64.    char *name;
  65.    int (*function)();
  66. } dictionary;
  67.       
  68. The elements of the structure are:
  69.  
  70.   - name     The function's name, as it should be known to REXX, in the form of
  71.              a null-terminated string.  The name should be in uppercase.
  72.   - function The address of the function; a value of type int (*)(char *,int).
  73.  
  74. The last element of the array of dictionary structures should have both
  75. fields set to a NULL pointer.
  76.  
  77. Once a function is called, it is loaded into the interpreter together will
  78. all the functions listed in the dictionary, if any, and future calls will
  79. not have to be loaded from a file.
  80.  
  81. Each function receives as its parameters the name by which it was called and
  82. the number of arguments supplied in the Rexx call to the function.  The name
  83. is given in upper case and without any leading directory names (for instance
  84. "/direct/file"(3) gives "FILE" as the name parameter).  Because this is
  85. given it is possible to fill in the "function" elements of several directory
  86. entries with the same address: the C function at that address uses the name
  87. parameter to ascertain which Rexx function was used.
  88.  
  89. Each function should delete all its arguments from the calculator stack,
  90. and then either return 0, or stack an answer and return 1.  This condition
  91. is relaxed if an error occurs: the function should then either die or return
  92. a negative number indicating the error condition.  A list of error numbers
  93. is defined in const.h, including Ecall for "Incorrect call to routine".
  94.  
  95. The arguments are placed on the calculator stack in LIFO order; that is, the
  96. last argument will be the first to be unstacked.  Each argument is either a
  97. string or a null argument.  A null argument has its length set to -1.
  98.  
  99. Useful functions, including functions to retrieve arguments and stack the
  100. answer, are the following:
  101.  
  102. char *delete(len)  int *len;
  103.  
  104. Deletes a string from the calculator stack, and returns an address where it
  105. can be found.  On return, len will be set to the length of the argument.
  106. The string is guaranteed to be followed by two bytes of available memory, so
  107. that it can be null-terminated if necessary, and the string may be written
  108. to.  The string is not guaranteed to be null-terminated when it is
  109. unstacked.  The string is not actually moved in memory, so it may be
  110. invalidated whenever the calculator stack is changed (that means that it may
  111. not be used as an argument to stack()).  However, further calls to delete()
  112. will not corrupt the string.
  113.  
  114. int getint(flag)  int *flag;
  115.  
  116. Deletes a string from the calculator stack, interprets it as an integer, and
  117. returns the result.  If the string is not a number which can be held in an
  118. int variable, the function will die.  If the string is not an integer and
  119. the flag is non-zero, the function will die, otherwise the number will be
  120. converted into the nearest integer.
  121.  
  122. void stack(string,len)  char *string; int len;
  123.  
  124. Copies the given string of the given length on to the calculator stack.
  125.  
  126. void stackint(i)  int i;
  127.  
  128. Stacks a string representing the integer i on the calculator stack.
  129.  
  130. int isnull()
  131.  
  132. Returns 1 if the next value to be unstacked is null, and zero otherwise.
  133.  
  134. void die(rc)  int rc;
  135.  
  136. Raise the error whose code is rc.  The interpreter will then either halt
  137. with diagnostics or signal to an appropriate label, according to the current
  138. settings of "SIGNAL ON".  This function never returns to its caller.
  139.  
  140. int num(minus,exp,zero,len)  int *minus,*exp,*zero,*len;
  141.  
  142. Attempts to extract a number from the top value on the calculator stack,
  143. returning it as a sequence of digits.  The value is always left stacked.  If
  144. unsuccessful, num returns a negative number (except when the top value is
  145. null, in which case num dies).  Otherwise, num stores a sequence of digits
  146. in the workspace (see below), and returns the offset from the start of the
  147. workspace to the start of the sequence of digits (which always equals the
  148. old value of eworkptr).  The value eworkptr is updated to point past the end
  149. of the sequence of digits.  The length of the sequence is returned in len.
  150. If the number is zero, then zero is set to 1, and otherwise it is set to 0.
  151. If it is negative, then minus is set to 1, and otherwise 0.  The exponent
  152. stored in exp is such that if a decimal point were placed between the first
  153. two digits of the sequence and the result were multiplied by ten to the
  154. power exp, then the original number would be recovered.
  155.  
  156. void stacknum(num,len,exp,minus) char *num; int exp,len,minus;
  157.  
  158. A sequence of digits starting at address num and of length len is formatted
  159. according to the Rexx rules for numerics and stacked.  The exponent "exp" and
  160. sign "minus" are interpreted according to the rules in "num" above.
  161.  
  162. char *varget(name,namelen,len) char *name; int varlen; int *len;
  163.  
  164. The variable whose name is "name" and contains "namelen" characters is
  165. searched for in the current symbol table.  If the name is a compound symbol
  166. or a stem, then the first character of the name must have bit 7 set.  The
  167. name is used as-is, that is, it is not translated to upper case, and if it
  168. is a compound variable then no substitution occurs in the tail.  A pointer
  169. to the variable's value is returned, and "len" is set to its length.  If the
  170. variable has not been assigned a value then "len" and the result are zero
  171. and the null pointer, respectively.  The copy of the value which is returned
  172. must not be changed in any way.  It may be invalidated whenever the symbol
  173. table is changed (and may not be used as a parameter to varset()).
  174.  
  175. void varset(name,namelen,value,len) char *name,*value; int namelen,len;
  176.  
  177. The parameters "name" and "namelen" name a variable and satisfy the same
  178. conditions as in varget above.  The parameters "value" and "len" describe
  179. the position and length respectively of a string which is to be assigned to
  180. the variable.  The assignment always succeeds unless there is insufficient
  181. memory available, in which case the routine dies.
  182.  
  183. Note: the variable name and the string may contain arbitrary characters, and
  184. neither is validated.  If you assign a value to a simple symbol called, e.g.
  185. "blah" (in lower case) or "XYZ.123" (containing a dot), etc.  then the
  186. symbol will not be accessible to the Rexx program, but it may be recovered
  187. using varget(), provided it has not been hidden or destroyed by a PROCEDURE
  188. instruction.
  189.  
  190. Any other function from the Rexx source may be used, but they are [or
  191. perhaps are not!] described elsewhere.  Try in the source itself...
  192.  
  193. A function may use global data from Rexx.  It may either #include "ext.h"
  194. (which defines all the global variables of the Rexx interpreter) or simply
  195. include declarations for the particular variables it uses.  Some useful
  196. variables are:
  197.  
  198. char *workptr; unsigned eworkptr,worklen;
  199.  
  200. The workspace, which may be used freely by a function.  The space starts at
  201. workptr, and is of maximum length worklen.  The variable eworkptr may be
  202. used to hold the length of the data currently stored in the workspace.
  203.  
  204. int precision,fuzz;
  205.  
  206. The setting of "NUMERIC DIGITS", and precision minus the setting of "NUMERIC
  207. FUZZ", respectively.  That is, "precision" holds the precision of ordinary
  208. calculations, and "fuzz" holds the precision of comparison operations.
  209.  
  210. char numform;
  211.  
  212. Zero if "NUMERIC FORM SCIENTIFIC" is in effect, and one if "NUMERIC FORM
  213. ENGINEERING".
  214.  
  215. int ppc;
  216.  
  217. The number of the instruction being interpreted.
  218.  
  219. int rxstacksock;
  220.  
  221. A file descriptor which is connected to the Rexx stack process via a socket.
  222.  
  223. FILE *ttyin,*ttyout;
  224.  
  225. Streams which may be used to communicate with the terminal.
  226.  
  227.  
  228. A Rexx memory structure (for example the workspace) may be extended using
  229. the macros mtest or dtest.  These are called like functions, but note that
  230. some arguments are evaluated more or less than once.
  231.  
  232. mtest(memptr,alloc,length,extend)
  233.  
  234. Check that the desired length for the area, "length", is not greater than
  235. the actual length, "alloc".  If it is, then attempt to reallocate the area,
  236. pointed to by "memptr", with "extend" more bytes than its previous length.
  237. The parameters memptr and alloc will be updated to reflect the new position
  238. and length of the area.  The macro will die if not enough memory is
  239. available.
  240.  
  241. dtest(memptr,alloc,length,extend)
  242.  
  243. Perform mtest on the four arguments, but return 0 if the area did not move,
  244. and non-zero otherwise.  In order to use this macro, the current function
  245. must contain variables:
  246.  
  247. char *mtest_old;
  248. long mtest_diff;
  249.  
  250. If the memory pointer has moved, then mtest_diff contains the difference
  251. (the new pointer minus the old).
  252.  
  253.  
  254. 2. Accessing the REXX stack
  255.  
  256.  (a) Initialising
  257.  
  258.      When the application which requires access to the stack initialises, or
  259.      when it first wants to use the stack, it should do the following:
  260.  
  261.      i.  If the environment variable RXSTACK is set, then a stack already
  262.      exists and uses a socket whose name is the value of RXSTACK.  This
  263.      should always happen if the application is called from within
  264.      REXX.  The application may choose to use this stack, or create
  265.      another.
  266.      ii. In order to create a new stack, the application should run "rxque"
  267.      and store the output.  If the application prefers a particular
  268.      filename for the stack socket, it should give that as a parameter
  269.      to "rxque" and also set the environment variable RXSTACK to that
  270.      name.  The output from "rxque filename" will be the stack's process
  271.      number in the format "%d\n".  The output from "rxque" will be in
  272.      the form "RXSTACK=%s RXSTACKPROC=%d".  The "%s" in this format is
  273.      the stack's socket name, and the "%d" is the stack's process number.
  274.      The RXSTACK variable must be exported to the environment.  The
  275.      process number must be remembered, so that the stack can be
  276.      terminated later.
  277.      iii.When a socket name has been obtained, the application should
  278.          connect to it a socket of type SOCK_STREAM.  This socket will be
  279.      used in all further communication with the stack.
  280.  
  281.      The stack obtained by the application in this way can be accessed by
  282.      any other process, providing it knows the socket name and has
  283.      permission to access it.  This will usually be limited to descendants
  284.      of the application.  In particular, if the application executes the
  285.      REXX interpreter, the interpreter will use the same stack.
  286.  
  287.  (b) Terminating
  288.  
  289.      If the application did not create the stack, it has nothing further to
  290.      do.  Otherwise it must kill the stack process (using the pid which was
  291.      remembered earlier) with signal 15 (SIGTERM).
  292.  
  293.      In case the application crashes, the stack process will terminate after
  294.      five minutes of inactivity if it finds that its parent no longer
  295.      exists (that means that when the stack server is executed it should be
  296.      executed as a child of the application, and not a grandchild or other
  297.      descendant).
  298.  
  299.  (c) Communications
  300.  
  301.      There are three data types which may be communicated: commands, lengths
  302.      and data.  A command is a single character.  A length is a sequence of
  303.      six hex digits followed by a newline character: seven bytes in all.
  304.      Data is an arbitrary sequence of characters of a pre-determined
  305.      length.  All communications are written unbuffered.
  306.  
  307.      Each communication with the stack Each is initiated by the application
  308.      writing a command character down the socket.  The possible command
  309.      characters are as follows:
  310.  
  311.      N (for Number):  The stack responds by writing a length down the
  312.        socket, representing the number of items on the stack.
  313.      S (for Stack):  The stack expects the application to write a length
  314.        value followed by a data item of that length.  It stacks that data
  315.        item in lifo order.
  316.      Q (for Queue):  The stack expects the application to write a length
  317.        value followed by a data item of that length.  It queues that data
  318.        item in fifo order.
  319.      G (for Get):  The stack responds by writing the length of the top stack
  320.        entry followed by its data, and removes the entry from the stack.
  321.      P (for Peek):  The stack responds by writing the length of the top stack
  322.        entry followed by its data, but leaves the stack unchanged.
  323.      D (for Drop):  No further communication occurs, but the stack deletes
  324.        its top entry.
  325.      K (for Kill me): The stack expects the application to write a length
  326.        value followed by one more byte.  The length value is interpreted as
  327.        the pid of a process, and the byte as a signal number.  On receipt of
  328.        this information, the stack server will (attempt to) kill the given
  329.        process with the given signal.  This command may be used to make an
  330.        application allow the stack to catch up, in case some of the
  331.        communications are still en route to the server (the Num command could
  332.        also be used for this purpose).
  333.  
  334.      If the stack process receives an incorrect command value or encounters
  335.      an error while reading from the socket, then the connection to the
  336.      offending application will be broken immediately.
  337.  
  338. 3. The REXX internal data structures
  339.  
  340. REXX has several data structures including the program, the label table, the
  341. symbol table, and the program stack.  Each is kept as a block of "malloc"ed
  342. memory which is grown dynamically as necessary (the "growing" is usually
  343. performed by the mtest and dtest macros, mentioned above).
  344.  
  345. (a) The Source
  346.  
  347.     The source code is stored in memory as it appears in the REXX program
  348.     on disk, except that newline characters are translated into zero bytes.
  349.     The address of each line (numbered from 1 to the number of lines in the
  350.     program) is stored in an array (which is another block of "malloc"ed
  351.     memory), and accessed using the construction "source[num]".  The
  352.     zeroth element of source stores the file name of the source, which is
  353.     stored in a separately allocated block of memory.  The block allocated
  354.     for the source itself is guaranteed to start at source[1].
  355.  
  356. (b) The Program
  357.  
  358.     The "program", or preprocessed source, is stored as a list of
  359.     instructions, and prog[num] is a structure containing details about the
  360.     "num"th instruction.  There are "stmts" instructions in this list.  Note
  361.     that "THEN", "ELSE" and "OTHERWISE" are counted as individual
  362.     instructions, and that null clauses do not appear in the list of
  363.     instructions.  prog[0] contains some pointers to the starts of things
  364.     (namely the block allocated for the tokenised program itself, the block
  365.     allocated for the source, and the beginning of the first comment in the
  366.     source).  prog[stmts] is a null instruction which points to the end of
  367.     the source.
  368.     
  369.     Each instruction is obtained from the source by removing all comments
  370.     and labels; stripping all unnecessary blanks and collapsing multiple
  371.     spaces into one; concatenating lines together whenever the continuation
  372.     character "," appears; tokenising keywords into special characters, and
  373.     translating "^" (the variant NOT operator) into "\" (the real NOT
  374.     operator).  The source is also checked for mismatched quotes, invalid
  375.     labels and invalid characters during preprocessing.
  376.  
  377.     Whereas "source" always contains the source of the program being
  378.     interpreted, "prog" can sometimes contain the list of instructions
  379.     obtained from an "interpret" instruction.  In this case, the source
  380.     pointer in prog[0] is used instead of source[1] when freeing the source.
  381.     Also, certain instructions (such as "call") are required to save the
  382.     current program temporarily and go back to the original program, by
  383.     searching for it on the program stack.
  384.  
  385.     The current instruction number within the program is stored in the global
  386.     variable ppc.  The current character position within the program line is
  387.     stored in a local variable, often called lineptr.
  388.  
  389.     Each prog[num] consists of the following structure, called "program":
  390.  
  391.        int num;         The line number in the source where the instruction
  392.                         originates - used when tracing source instructions.
  393.        char *source;    The start of this instruction in the source
  394.        char *sourcend;  The end of this instruction in the source
  395.        int related;     Reserved for future use
  396.        char *line;      The address of the tokenised instruction
  397.  
  398.     The source between "source" and "sourcend" is the current instruction
  399.     including any comments on the same line but not including labels.
  400.     Comments on separate lines and labels will appear after "sourcend" or
  401.     before "source".
  402.  
  403. (c) The Labels    
  404.  
  405.     Labels within a program are separated off and stored in a table while
  406.     the program is being preprocessed.  The table is stored in a block of
  407.     memory at address labptr and of length lablen.  While the table is being
  408.     built up the length of data so far is elapbtr.  The table consists of
  409.     the concatenation of elements in the following format:
  410.  
  411.        int    total length of this element
  412.        int    instruction number of label
  413.        char[] name of label, terminated with a zero character and padded [*]
  414.  
  415.     The last element in the table is followed by the integer zero.
  416.  
  417.     [*] In all the data structures used by REXX/imc, variable-length string
  418.     entries are padded (with random bytes) to a multiple of 4 bytes, in
  419.     order that later data is aligned to the Sun SPARCstation's requirements.
  420.     The alignment is done by macros in const.h and may be changed.
  421.  
  422. (d) The Calculator Stack
  423.  
  424.     The calculator stack is simply a list of values in temporary storage
  425.     during the evaluation of an expression.  Expressions are in effect
  426.     translated to reverse polish notation (e.g. 1+2 becomes 1 2 +), with
  427.     each operation stacking and removing values as appropriate.  The stack
  428.     is stored in a block of memory addressed by cstackptr and of cstacklen
  429.     bytes.  The total size of the data on the stack is ecstackptr.  Each
  430.     element on the stack consists of a string (padded as necessary [*])
  431.     followed by its integer length.
  432.  
  433. (e) The Workspace
  434.  
  435.     The workspace is a block of memory which is used by various parts of the
  436.     interpreter to store transient data.  It is addressed by workptr and is
  437.     of length worklen.  Some routines (especially num()) maintain the length
  438.     of the currently stored data in eworkptr.
  439.  
  440. (f) The Symbol Table
  441.  
  442.     The symbol table is a multiple-level associative array containing the
  443.     definitions of all the REXX symbols which have been assigned values.  It
  444.     is stored in a block of memory addressed by vartab and of length varlen.
  445.  
  446.     Each level of the table is a separate entity, referring to the active
  447.     variables of a program fragment which used the PROCEDURE instruction to
  448.     hide the earlier levels, except that each level may contain pointers to
  449.     earlier levels as a result of the PROCEDURE EXPOSE instruction.
  450.  
  451.     The start of each level is stored in the array varstk[] as an integer
  452.     offset from the start of the entire table.  The number of levels is
  453.     varstkptr, and the number of elements in the array is varstklen.  The
  454.     total length of all current levels of the symbol table is
  455.     varstk[varstkptr+1].
  456.  
  457.     Each level of the symbol table contains all currently active simple
  458.     symbols and stems as a binary search tree.  The elements of the tree are
  459.     in the following format (as described by the varent data type):
  460.  
  461.        int    total length of this element
  462.        int    position of the left child (as offset from start of level)
  463.        int    position of the right child (as offset from start of level)
  464.        int    length of the symbol's name
  465.        int    amount of memory allocated to hold the symbol's value
  466.        int    actual length of the symbol's value
  467.        char[] the symbol's name, padded [*]
  468.        char[] space for the symbol's value
  469.  
  470.     If the symbol is a stem, the terminating dot of the name is not stored,
  471.     but the most significant bit of the first character of the name is set.
  472.  
  473.     If the length of the value is negative, then the symbol is considered
  474.     to be undefined; it has been deleted by DROP or some other process.
  475.  
  476.     If the "amount of memory" element of the structure is negative, then
  477.     this symbol is actually located in an earlier level; the negative value
  478.     gives the level number, starting at -1 which means the earliest level
  479.     (i.e. the first in the memory block).
  480.  
  481.     Each stem entry in the symbol table has a value containing a default
  482.     value and a mini-symbol table.  The default value is stored first, in
  483.     the format:
  484.  
  485.        int    the amount of space allocated to the default value
  486.        int    the actual length of the default value
  487.        char[] space for the default value
  488.  
  489.     Immediately following that are entries for all the tails, in exactly the
  490.     same format as for the main symbol table.
  491.  
  492. (g) The Program Stack
  493.  
  494.     The program stack holds information relating to currently active control
  495.     structures, e.g. function calls and DO-END blocks.  It is stored in a
  496.     block of memory addressed by pstackptr and of length pstacklen.  The
  497.     length of all data currently on the program stack is epstackptr.  The
  498.     stack holds a sequence of various entries in the following formats, and
  499.     the number of entries in the current function is held in pstacklev:
  500.  
  501.     for a simple DO-END block (type 0), a SELECT block (type 2),
  502.     a DO WHILE or DO FOREVER block or (type 8), a "struct minstack" entry:
  503.  
  504.        int stmt    the statement number where the block started
  505.        char *pos   the character where the block started (used for finding the
  506.                    WHILE or UNTIL part of a repetitive DO instruction)
  507.        int len     the length of this structure (16)
  508.        int type    the type value (as mentioned above)
  509.  
  510.     for a repetitive DO with a control variable, an extended "struct
  511.     minstack" entry:
  512.  
  513.        int stmt    the statement number where the block started
  514.        char *pos   the character where the block started
  515.        char[]      the limit value, padded [*] (empty string for "no limit")
  516.        int         the length of the limit value
  517.        char[]      the step value, padded [*]
  518.        int         the length of the step value
  519.        char[]      the name of the control variable, padded [*]
  520.        int         the length of the control variable name
  521.        int         the value which appeared after FOR, or -1 for "no value"
  522.        int len     the total length of this structure
  523.        int type    the number 10.
  524.  
  525.     for a repetitive block introduced by "DO count", a "struct forstack" entry:
  526.  
  527.        int stmt    the statement number where the block started
  528.        char *pos   the character where the block started
  529.        int fornum  the value specified after "DO"
  530.        int len     the length of this structure (20)
  531.        int type    the number 15.
  532.  
  533.     for an internal function call, a "struct procstack2" entry:
  534.  
  535.        int stmt    the statement number where the function call ocurred
  536.        char *csp   the caller's cstackptr
  537.        int ecsp    the caller's ecstaclptr
  538.        int csl     the caller's cstacklen
  539.        char trc    the caller's trace flag
  540.        char tim    the caller's timestamp flag
  541.        char form   the caller's NUMERIC FORM (0 for SCIENTIFIC)
  542.                    the compiler will probably insert one byte here
  543.        int digits  the caller's NUMERIC DIGITS
  544.        int fuzz    the caller's "NUMERIC DIGITS minus NUMERIC FUZZ"
  545.        long mic    the caller's timestamp microseconds value
  546.        long sec    the caller's timestamp seconds value
  547.        program *prg the program which was being interpreted at the time
  548.        int stmts   the number of statements in that program
  549.        int len     the length of this structure (52)
  550.        int type    the number 11, becoming 12 when the PROCEDURE instruction
  551.                    has been executed
  552.     Note: the program is stored in case it was generated by "interpret"; if
  553.     that is so then the "real" program will be reinstated before the call.
  554.  
  555.     for an external function call, a "struct procstack" entry:
  556.  
  557.        int stmt    the statement number where the function call ocurred
  558.        char *csp   the caller's cstackptr
  559.        int ecsp    the caller's ecstaclptr
  560.        int csl     the caller's cstacklen
  561.        char trc    the caller's trace flag
  562.        char tim    the caller's timestamp flag
  563.        char form   the caller's NUMERIC FORM (0 for SCIENTIFIC)
  564.                    the compiler will probably insert one byte here
  565.        int digits  the caller's NUMERIC DIGITS
  566.        int fuzz    the caller's "NUMERIC DIGITS minus NUMERIC FUZZ"
  567.        long mic    the caller's timestamp microseconds value
  568.        long sec    the caller's timestamp seconds value
  569.        program *prg the caller's program
  570.        int stmts   the caller's number of instructions
  571.        int lines   the caller's number of program lines
  572.        char *src   the caller's source
  573.        char *lab   the caller's labptr
  574.        int lev     the caller's pstacklev
  575.        int len     the length of this structure (68)
  576.        int type    the number 13.
  577.  
  578.     for an INTERPRET instruction, a "struct interpstack" entry:
  579.  
  580.        int stmt     the statement number where the INTERPRET occurred
  581.        program *prg the program which was being interpreted at the time
  582.        int stmts    the number of instructions in that program
  583.        int len      the length of this structure (20)
  584.        int type     the number 14.
  585.  
  586.     for a command typed during interactive trace mode, a "struct
  587.     interactstack" entry (note that a "struct interpstack" entry also
  588.     appears above this):
  589.  
  590.        int stmt    the statement number where the interruption occurred
  591.        char *csp   the interrupted program's cstackptr
  592.        int ecs     the interrupted program's ecstackptr
  593.        int csl     the interrupted program's cstacklen
  594.        int len     the length of this structure (16)
  595.        int type    the number 16.
  596.  
  597.     Occasionally, the interpreter stacks a program line with the sole intent
  598.     of having it appear in the traceback.  Such an entry would be in the
  599.     format of a "struct errorstack":
  600.  
  601.        int stmt     the statement number where the error occurred
  602.        program *prg the program where the error occurred
  603.        int stmts    the number of statements in this program
  604.        int len      the length of this structure (20)
  605.        int type     the number 20
  606.        
  607. (h) The "Hash" Tables
  608.  
  609.     There are three "hash" tables, each arranged in a similar way to one
  610.     level of the symbol table; however the value of each symbol in the hash
  611.     table is a single void* pointer rather than a string of characters.
  612.     There are three hash tables, each occupying a separate block of memory
  613.     addressed by hashptr[i] and of length hashlen[i] (for i=0,1,2).  They
  614.     are used to store environment variables, details of open files, and
  615.     details about loaded functions respectively.  Each element of a hash
  616.     table is arranged as follows (and as indicated in the "hashent" data
  617.     type):
  618.  
  619.        int    length of this element
  620.        int    position of the left child
  621.        int    position of the right child
  622.        void*  value of the element
  623.        char[] name of the element, terminated by a zero byte and padded [*]
  624.  
  625.     The value of each element may be one of the following:
  626.  
  627.     In hash table 0:  a pointer to the string "NAME=VALUE" which has been
  628.     used in a putenv() call.
  629.  
  630.     In hash table 1:  either a null pointer, or a pointer to a block of
  631.     memory which contains a "struct fileinfo" followed by a zero-terminated
  632.     filename (which may be empty if the file name is unknown).  The "struct
  633.     fileinfo" is described in const.h.
  634.  
  635.     In hash table 2:  a pointer to a "funcinfo" structure containing the
  636.     address of a loaded function.  One of the functions loaded from each
  637.     function package also contains the handle which was returned from
  638.     dlopen().
  639.  
  640. (i) The Signal Stack
  641.  
  642.     REXX stores the context of each invocation of the interpreter()
  643.     function, so that it can be restored whenever an EXIT or a caught signal
  644.     is encountered.  The context is stored in the array sigstack[], which at
  645.     any time has sigstacklen elements allocated to it.  The number of the
  646.     highest used element of sigstack[] is interplev.  Each entry of the
  647.     signal stack contains:
  648.  
  649.        short bits    The combined bits for all SIGNAL ON traps which are on
  650.        short bitson  ...all SIGNAL ON traps which were executed at this level
  651.        short callon  ...all CALL ON traps which are on
  652.        short delay   ...all conditions which are delayed
  653.        char type     1 if a "signal" trap just occurred, 2 if "call", 0 if none
  654.        char which    The number for the condition which just occurred (if any)
  655.        char *data    A description for for the condition which just occurred
  656.        int ppc[6]    The statement numbers to jump to for all the conditions
  657.                      or minus the statement number to flag with "label not
  658.              found" if a condition occurs
  659.        jmp_buf jmp   The context of this level of the interpreter.
  660.  
  661.     Note: a negative number in ppc[i] means that the trap instruction for
  662.     this condition named a non-existent label.  -ppc[i] will be the
  663.     statement number of this trap instruction.  This means that we can
  664.     delay the "label not found" error until it actually happens: moreover,
  665.     we can include the condition trap instruction in the traceback.
  666.     However, an interpreted condition trap instruction is not guaranteed to
  667.     stay around, and therefore it is reported as an error immediately if it
  668.     names a non-existent label.
  669.  
  670. (j) The Shell's Hash Table
  671.  
  672.     The builtin shell keeps a record of where it found each command in a
  673.     hash table (yes, a real one ;-) ).  The variable "hashtable" points to
  674.     an array of bucket pointers, and the variable "hashbuckets" holds the
  675.     number of pointers in the table.  A bucket pointer is null if there are
  676.     no entries in the bucket; otherwise it points to a hashitem structure,
  677.     representing the first item in the bucket.  That item may in turn point
  678.     to another item in the bucket.  The items in each bucket are kept in
  679.     alphabetical order, to reduce the average time taken for an unsuccessful
  680.     search (or an insertion).  Each item contains the following information:
  681.  
  682.        struct _hashitem *next  The next item in the bucket, or null
  683.        int hits                Number of times this has been found
  684.        int expense             Position within $PATH
  685.        int dot                 Whether dot occurred in the path before this
  686.        int data                Offset from end of header to data
  687.        char[]                  The key; a string of characters ending with 0.
  688.        char[]                  The data; another nul-terminated string.
  689.